package com.powernode.controller;

import com.powernode.domain.SysMenu;
import com.powernode.model.Result;
import com.powernode.model.SecurityUser;
import com.powernode.service.SysMenuService;
import com.powernode.utils.AuthUtils;
import com.powernode.vo.MenuAndAuth;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.web.bind.annotation.*;

import java.util.List;
import java.util.Set;

/**
 * 系统权限控制层
 */
@Api(tags = "系统权限接口管理")
@RequestMapping("sys/menu")
@RestController

public class SysMenuController {
    @Autowired
    private SysMenuService sysMenuService;

    @ApiOperation("查询登录用户的菜单和权限")
    @GetMapping("nav")
    public Result<MenuAndAuth> loadUserMenuAndPerms() {
        //获取当前登录用户的标识
/*        SecurityUser securityUser = (SecurityUser) SecurityContextHolder.getContext().getAuthentication().getPrincipal();
        Long userId = securityUser.getUserId();*/
        Long loginUserId = AuthUtils.getLoginUserId();

        //根据用户标识查询操作权限集合
        Set<String> perms = AuthUtils.getPerms();

        Set<SysMenu> menus = sysMenuService.queryUserMenuListByUserId(loginUserId);

        //创建菜单和操作权限对象
        MenuAndAuth menuAndAuth = new MenuAndAuth(menus, perms);
        return Result.success(menuAndAuth);
    }


    /**
     * 查询系统所有权限集合
     * <p>
     * 该接口通过GET请求方式提供系统所有权限的列表数据。它要求调用者具备'sys:menu:list'权限，
     * 以确保只有授权的用户可以访问系统的权限集合信息。
     *
     * @return 包含系统所有权限的列表Result对象，成功时返回权限列表，失败时返回相应的错误信息。
     */
    @ApiOperation("查询系统所有权限集合")
    @GetMapping("table")
    @PreAuthorize("hasAuthority('sys:menu:list')")
    public Result<List<SysMenu>> loadAllSysMenuList() {
        List<SysMenu> list = sysMenuService.queryAllSysMenuList();
        return Result.success(list);
    }

    // 使用ApiOperation注解描述该方法的主要功能，即新增权限
    @ApiOperation("新增权限")
    // 使用PostMapping注解指定该方法处理POST请求
    @PostMapping
    // 使用PreAuthorize注解指定访问该方法需要具备的权限，即拥有'sys:menu:save'权限才能访问
    @PreAuthorize("hasAuthority('sys:menu:save')")
    public Result<String> saveSysMenu(@RequestBody SysMenu sysMenu) {
        // 调用sysMenuService的saveSysMenu方法保存权限信息，返回保存结果
        Boolean saved = sysMenuService.saveSysMenu(sysMenu);
        // 根据保存结果调用Result.handle方法生成相应的结果对象
        return Result.handle(saved);
    }

    /**
     * 根据标识查询权限
     * 该方法通过菜单标识（menuId）来查询具体的权限信息它使用了Spring Security的PreAuthorize注解，
     * 确保只有拥有相应权限的用户才能访问这个接口
     *
     * @param menuId 菜单标识，用于指定要查询的权限
     * @return 返回一个Result对象，其中包含查询到的权限信息
     */
    @ApiOperation("根据标识查询权限")
    @GetMapping("info/{menuId}")
    @PreAuthorize("hasAuthority('sys:menu:info')")
    public Result<SysMenu> loadSysMenuInfo(@PathVariable Long menuId) {
        // 根据菜单标识查询权限信息
        SysMenu sysMenu = sysMenuService.getById(menuId);
        // 返回查询结果，使用Result对象包装
        return Result.success(sysMenu);
    }


    /**
     * 修改菜单权限信息
     * 通过PUT请求更新系统菜单信息，此操作需要具有特定权限的用户才能执行
     * 使用@PreAuthorize注解限制只有拥有'sys:menu:update'权限的用户才能访问此方法
     *
     * @param sysMenu 包含要更新的菜单信息的SysMenu对象，通过请求体(@RequestBody)传递
     * @return 返回一个Result对象，其中包含操作结果信息，成功或失败的原因等
     */
    @ApiOperation("修改菜单权限信息")
    @PutMapping
    @PreAuthorize("hasAuthority('sys:menu:update')")
    public Result<String> modifySysMenu(@RequestBody SysMenu sysMenu) {
        Boolean modified = sysMenuService.modifySysMenu(sysMenu);
        return Result.handle(modified);
    }


    /**
     * 删除菜单权限
     * <p>
     * 通过菜单ID删除对应的菜单权限，需要具备特定权限才能执行此操作
     * </p>
     *
     * @param menuId 菜单的ID，用于标识要删除的菜单权限
     * @return 删除操作的结果，包括是否成功等信息
     */
    @ApiOperation("删除菜单权限")
    @DeleteMapping("{menuId}")
    @PreAuthorize("hasAuthority('sys:menu:delete')")
    public Result<String> removeSysMenu(@PathVariable Long menuId) {
       // 调用服务层方法，根据菜单ID删除菜单权限
       Boolean removed = sysMenuService.removeSysMenuById(menuId);
       // 处理删除结果，封装为统一的结果对象并返回
        return Result.handle(removed);
    }

}
